home *** CD-ROM | disk | FTP | other *** search
/ Technotools / Technotools (Chestnut CD-ROM)(1993).ISO / os2tools / bnklysrc / sched.c < prev    next >
C/C++ Source or Header  |  1989-02-25  |  18KB  |  586 lines

  1. /*--------------------------------------------------------------------------*/
  2. /*                                                                          */
  3. /*                                                                          */
  4. /*      ------------         Bit-Bucket Software <no-Inc>                   */
  5. /*      \ 10001101 /         Writers and Distributors of                    */
  6. /*       \ 011110 /          No-Cost<no-tm> Software.                       */
  7. /*        \ 1011 /                                                          */
  8. /*         ------                                                           */
  9. /*                                                                          */
  10. /*  Copyright (C) 1987, 1988, 1989 by Robert Hartman and Vincent Perriello  */
  11. /*                                                                          */
  12. /*                                                                          */
  13. /*                 This module was written by Bob Hartman                   */
  14. /*                                                                          */
  15. /*                                                                          */
  16. /*                     BinkleyTerm Scheduler Routines                       */
  17. /*                                                                          */
  18. /*                                                                          */
  19. /*    For complete  details  of the licensing restrictions, please refer    */
  20. /*    to the License  agreement,  which  is published in its entirety in    */
  21. /*    the MAKEFILE and BT.C, and also contained in the file LICENSE.210.    */
  22. /*                                                                          */
  23. /*    USE  OF THIS FILE IS SUBJECT TO THE  RESTRICTIONS CONTAINED IN THE    */
  24. /*    BINKLEYTERM  LICENSING  AGREEMENT.  IF YOU DO NOT FIND THE TEXT OF    */
  25. /*    THIS  AGREEMENT IN ANY OF THE  AFOREMENTIONED FILES,  OR IF YOU DO    */
  26. /*    NOT HAVE THESE FILES,  YOU SHOULD  IMMEDIATELY CONTACT THE AUTHORS    */
  27. /*    AT THE  ADDRESSES LISTED BELOW.  IN NO EVENT SHOULD YOU PROCEED TO    */
  28. /*    USE   THIS  FILE  WITHOUT  HAVING   ACCEPTED  THE  TERMS  OF   THE    */
  29. /*    BINKLEYTERM  LICENSING AGREEMENT,  OR SUCH OTHER  AGREEMENT AS YOU    */
  30. /*    ARE ABLE TO REACH WITH THE AUTHORS.                                   */
  31. /*                                                                          */
  32. /*                                                                          */
  33. /*    The Authors can be reached at the following addresses:                */
  34. /*                                                                          */
  35. /*    Robert C. Hartman                      Vincent E. Perriello           */
  36. /*    Spark Software                         VEP Software                   */
  37. /*    427-3 Amherst Street                   111 Carroll Street             */
  38. /*    CS2032, Suite 232                      Naugatuck, CT 06770            */
  39. /*    Nashua, NH 03061                                                      */
  40. /*                                                                          */
  41. /*    FidoNet 1:132/101                      FidoNet 1:141/491              */
  42. /*    Data    (603) 888-8179                 Data    (203) 729-7569         */
  43. /*                                                                          */
  44. /*    Please feel free to contact us at any time to share your comments     */
  45. /*    about our software and/or licensing policies.                         */
  46. /*                                                                          */
  47. /*--------------------------------------------------------------------------*/
  48.  
  49. #include <stdio.h>
  50. #include <ctype.h>
  51. #include <sys/types.h>
  52. #include <sys/stat.h>
  53. #include <string.h>
  54. #include <stdlib.h>
  55. #include <process.h>
  56. #include <time.h>
  57.  
  58. #ifdef __TURBOC__
  59. #include "tc_utime.h"
  60. #include <alloc.h>
  61. #include <mem.h>
  62. #else
  63. #include <sys/utime.h>
  64. #include <malloc.h>
  65. #include <memory.h>
  66. #endif
  67.  
  68. #include "com.h"
  69. #include "xfer.h"
  70. #include "zmodem.h"
  71. #include "keybd.h"
  72. #include "sbuf.h"
  73. #include "sched.h"
  74. #include "externs.h"
  75. #include "prototyp.h"
  76.  
  77. static void write_stats (void);
  78.  
  79.  
  80. /**************************************************************************/
  81. /*** This MUST be exactly 16 total bytes including the terminating null ***/
  82. /*** or the routines read_sched() and write_sched() must be changed!!!! ***/
  83. /**************************************************************************/
  84. static char *BinkSched = "BinkSchedule 03";      /* Version of scheduler   */
  85.  
  86.  
  87. void find_event ()
  88. {
  89.    int cur_day;
  90.    int cur_hour;
  91.    int cur_minute;
  92.    int cur_mday;
  93.    int cur_mon;
  94.    int cur_year;
  95.    int junk;
  96.    int our_time;
  97.    int i;
  98.    char cmds[150];
  99.  
  100.    /* Get the current time in minutes */
  101.    dostime (&cur_hour, &cur_minute, &junk, &junk);
  102.    our_time = (cur_hour % 24) * 60 + (cur_minute % 60);
  103.  
  104.    /* Get the current day of the week */
  105.    dosdate (&cur_mon, &cur_mday, &cur_year, &cur_day);
  106.  
  107.    cur_day = 1 << cur_day;
  108.  
  109.    cur_event = -1;
  110.  
  111.    if (cur_mday != hist.which_day)
  112.       {
  113.       write_stats ();
  114.       memset (&hist, 0, sizeof (HISTORY));
  115.       hist.which_day = cur_mday;
  116.       if (un_attended && fullscreen)
  117.          {
  118.          do_today ();
  119.          sb_show ();
  120.          }
  121.       }
  122.  
  123.    /* Go through the events from top to bottom */
  124.    for (i = 0; i < num_events; i++)
  125.       {
  126.       if (our_time >= e_ptrs[i]->minute)
  127.          {
  128.          if ((cur_day & e_ptrs[i]->days) &&
  129.      ((!e_ptrs[i]->day) || (e_ptrs[i]->day == (char)cur_mday)) &&
  130.      ((!e_ptrs[i]->month) || (e_ptrs[i]->month == (char)cur_mon)))
  131.             {
  132.             if (((our_time - e_ptrs[i]->minute) < e_ptrs[i]->length) ||
  133.             ((our_time == e_ptrs[i]->minute) && (e_ptrs[i]->length == 0)) ||
  134.                 ((e_ptrs[i]->behavior & MAT_FORCED) && (e_ptrs[i]->last_ran != cur_mday)))
  135.                {
  136.                /* Are we not supposed to force old events */
  137.                if (((our_time - e_ptrs[i]->minute) > e_ptrs[i]->length) && (noforce))
  138.                   {
  139.                   e_ptrs[i]->last_ran = cur_mday;
  140.                   continue;
  141.                   }
  142.  
  143.                if (e_ptrs[i]->last_ran != cur_mday)
  144.                   {
  145.                   screen_blank = 0;
  146.                   set_xy ("");
  147.                   status_line (":Starting Event %d", i + 1);
  148.  
  149.                   more_mail = 1;
  150.  
  151.                   /* Mark that this one is running */
  152.                   e_ptrs[i]->last_ran = cur_mday;
  153.  
  154.                   /*
  155.                    * Mark that we have not yet skipped it. After all, it just
  156.                    * started! 
  157.                    */
  158.                   e_ptrs[i]->behavior &= ~MAT_SKIP;
  159.  
  160.                   /* Write out the schedule */
  161.                   write_sched ();
  162.  
  163.                   /* If we are supposed to exit, then do it */
  164.                   if (e_ptrs[i]->errlevel[0])
  165.                      {
  166.                      status_line ("#Exit at start of event with errorlevel %d",
  167.                                   e_ptrs[i]->errlevel[0]);
  168.  
  169.                      errl_exit (e_ptrs[i]->errlevel[0]);
  170.                      }
  171.                   else if (packer != NULL)
  172.                      {
  173.                      status_line ("#Running clean/pack sequence");
  174.                      mdm_init (modem_busy);
  175.                      DTR_OFF ();
  176.                      scr_printf ("\033[H\033[2J");
  177.                      vfossil_cursor (1);
  178.                      if (cleanup != NULL)
  179.                         {
  180.                         strcpy (cmds, cleanup);
  181.                         if (i >= 0)
  182.                            strcat (cmds, e_ptrs[i]->cmd);
  183.                         b_spawn (cmds);
  184.                         }
  185.                      strcpy (cmds, packer);
  186.                      if (i >= 0)
  187.                         strcat (cmds, e_ptrs[i]->cmd);
  188.                      b_spawn (cmds);
  189.                      if (fullscreen)
  190.                         {
  191.                         scr_printf ("\033[H\033[2J");
  192.                         sb_dirty ();
  193.                         opening_banner ();
  194.                         mailer_banner ();
  195.                         }
  196.                      DTR_ON ();
  197.                      mdm_init (modem_init);
  198.                      status_line ("#System re-enabled after clean/pack sequence");
  199.                      xmit_reset ();
  200.                      }
  201.  
  202.                   cur_event = i;
  203.  
  204.                   xmit_reset ();
  205.                   }
  206.                else
  207.                   {
  208.                   /* Don't do events that have been exited already */
  209.                   if (e_ptrs[i]->behavior & MAT_SKIP)
  210.                      continue;
  211.                   }
  212.  
  213.                cur_event = i;
  214.  
  215.                if (e_ptrs[i]->behavior & MAT_NOREQ)
  216.                   {
  217.                   matrix_mask &= ~TAKE_REQ;
  218.                   no_requests = 1;
  219.                   }
  220.                else
  221.                   {
  222.                   matrix_mask |= TAKE_REQ;
  223.                   no_requests = 0;
  224.                   }
  225.  
  226.                if (e_ptrs[i]->behavior & MAT_NOOUTREQ)
  227.                   {
  228.                   requests_ok = 0;
  229.                   }
  230.                else
  231.                   {
  232.                   requests_ok = 1;
  233.                   }
  234.  
  235.                max_connects = e_ptrs[i]->with_connect;
  236.                max_noconnects = e_ptrs[i]->no_connect;
  237.  
  238.                break;
  239.                }
  240.             }
  241.          }
  242.       }
  243. }
  244.  
  245. int what_event ()
  246. {
  247.    int cur_day;
  248.    int cur_hour;
  249.    int cur_minute;
  250.    int cur_mday;
  251.    int cur_mon;
  252.    int cur_year;
  253.    int junk;
  254.    int our_time;
  255.    int w_event;
  256.    int i;
  257.  
  258.    /* Get the current time in minutes */
  259.    dostime (&cur_hour, &cur_minute, &junk, &junk);
  260.    our_time = cur_hour * 60 + cur_minute;
  261.  
  262.    /* Get the current day of the week */
  263.    dosdate (&cur_mon, &cur_mday, &cur_year, &cur_day);
  264.  
  265.    cur_day = 1 << cur_day;
  266.  
  267.    w_event = -1;
  268.  
  269.    /* Go through the events from top to bottom */
  270.    for (i = 0; i < num_events; i++)
  271.       {
  272.       if (our_time >= e_ptrs[i]->minute)
  273.          {
  274.          if ((cur_day & e_ptrs[i]->days) &&
  275.      ((!e_ptrs[i]->day) || (e_ptrs[i]->day == (char)cur_mday)) &&
  276.      ((!e_ptrs[i]->month) || (e_ptrs[i]->month == (char)cur_mon)))
  277.             {
  278.             if (((our_time - e_ptrs[i]->minute) < e_ptrs[i]->length) ||
  279.             ((our_time == e_ptrs[i]->minute) && (e_ptrs[i]->length == 0)) ||
  280.                 ((e_ptrs[i]->behavior & MAT_FORCED) && (e_ptrs[i]->last_ran != cur_mday)))
  281.                {
  282.                /* Are we not supposed to force old events */
  283.                if (((our_time - e_ptrs[i]->minute) > e_ptrs[i]->length) && (noforce))
  284.                   {
  285.                   e_ptrs[i]->last_ran = cur_mday;
  286.                   continue;
  287.                   }
  288.  
  289.                if ((e_ptrs[i]->last_ran == cur_mday) &&
  290.                    (e_ptrs[i]->behavior & MAT_SKIP))
  291.                   {
  292.                   /* Don't do events that have been exited already */
  293.                   continue;
  294.                   }
  295.  
  296.                w_event = i;
  297.  
  298.                break;
  299.                }
  300.             }
  301.          }
  302.       }
  303.  
  304.    return (w_event);
  305. }
  306.  
  307. void read_sched ()
  308. {
  309.    char temp1[80], temp2[80];
  310.    EVENT *sptr;
  311.    struct stat buffer1, buffer2;
  312.    FILE *f;
  313.    int i;
  314.  
  315.    strcpy (temp1, BINKpath);
  316.    strcpy (temp2, BINKpath);
  317.    strcat (temp1, "Binkley.Scd");
  318.    strcat (temp2, "Binkley.Evt");
  319.  
  320.    if (stat (temp1, &buffer1))
  321.       {
  322.       return;
  323.       }
  324.  
  325.    if (stat (temp2, &buffer2))
  326.       {
  327.       strcpy (temp2, BINKpath);
  328.       strcat (temp2, config_name);
  329.       if (stat (temp2, &buffer2))
  330.          {
  331.          return;
  332.          }
  333.       }
  334.  
  335.    if ((buffer1.st_atime < buffer2.st_atime) ||
  336.        (buffer1.st_size < sizeof (EVENT)))
  337.       {
  338.       return;
  339.       }
  340.  
  341.    if ((sptr = (EVENT *) malloc ((int) buffer1.st_size - 16 - sizeof (HISTORY))) == NULL)
  342.       {
  343.       return;
  344.       }
  345.  
  346.    if ((f = fopen (temp1, "rb")) == NULL)
  347.       {
  348.       return;
  349.       }
  350.  
  351.    temp1[0] = '\0';
  352.    fread (temp1, 16, 1, f);
  353.    if (strcmp (temp1, BinkSched) != 0)
  354.       {
  355.       fclose (f);
  356.       return;
  357.       }
  358.  
  359.    fread (&hist, (int) sizeof (HISTORY), 1, f);
  360.    fread (sptr, (int) buffer1.st_size - 16 - sizeof (HISTORY), 1, f);
  361.    got_sched = 1;
  362.  
  363.    num_events = (int) ((buffer1.st_size - 16 - sizeof (HISTORY)) / sizeof (EVENT));
  364.    for (i = 0; i < num_events; i++)
  365.       {
  366.       e_ptrs[i] = sptr++;
  367.       }
  368.  
  369.    fclose (f);
  370.    return;
  371. }
  372.  
  373. void write_sched ()
  374. {
  375.    char temp1[80], temp2[80];
  376.    FILE *f;
  377.    int i;
  378.    struct stat buffer1;
  379.    struct utimbuf times;
  380.    long t;
  381.  
  382.    /* Get the current time */
  383.    t = time (NULL);
  384.  
  385.    strcpy (temp1, BINKpath);
  386.    strcpy (temp2, BINKpath);
  387.    strcat (temp1, "Binkley.Scd");
  388.    strcat (temp2, "Binkley.Evt");
  389.  
  390.    /* Get the current stat for .Evt file */
  391.    if (!stat (temp2, &buffer1))
  392.       {
  393.  
  394.       /*
  395.        * If it is newer than current time, we have a problem and we must
  396.        * reset the file date - yucky, but it will probably work 
  397.        */
  398.       if (t < buffer1.st_atime)
  399.          {
  400.          times.actime = buffer1.st_atime;
  401.          times.modtime = buffer1.st_atime;
  402.          status_line ("!Date rollover problem?");
  403.          }
  404.       else
  405.          {
  406.          times.actime = t;
  407.          times.modtime = t;
  408.          }
  409.       }
  410.  
  411.    if ((f = fopen (temp1, "wb")) == NULL)
  412.       {
  413.       return;
  414.       }
  415.  
  416.    fwrite (BinkSched, 16, 1, f);
  417.    fwrite (&hist, (int) sizeof (HISTORY), 1, f);
  418.  
  419.    for (i = 0; i < num_events; i++)
  420.       {
  421.       /* If it is skipped, but not dynamic, reset it */
  422.       if ((e_ptrs[i]->behavior & MAT_SKIP) &&
  423.           (!(e_ptrs[i]->behavior & MAT_DYNAM)))
  424.          {
  425.          e_ptrs[i]->behavior &= ~MAT_SKIP;
  426.          }
  427.  
  428.       /* Write this one out */
  429.       fwrite (e_ptrs[i], sizeof (EVENT), 1, f);
  430.       }
  431.  
  432.    fclose (f);
  433.  
  434.    utime (temp1, ×);
  435.  
  436.    return;
  437. }
  438.  
  439. static void write_stats ()
  440. {
  441.    char temp1[80];
  442.    FILE *f;
  443.  
  444.    strcpy (temp1, BINKpath);
  445.    strcat (temp1, "Binkley.Day");
  446.  
  447.    if ((f = fopen (temp1, "wb")) == NULL)
  448.       {
  449.       return;
  450.       }
  451.  
  452.    fwrite (&hist, (int) sizeof (HISTORY), 1, f);
  453.  
  454.    fclose (f);
  455.  
  456.    return;
  457. }
  458.  
  459. int time_to_next ()
  460. {
  461.    int cur_day;
  462.    int cur_hour;
  463.    int cur_minute;
  464.    int cur_mday;
  465.    int cur_mon;
  466.    int cur_year;
  467.    int junk;
  468.    int our_time;
  469.    int i;
  470.    int time_to;
  471.    int guess;
  472.    int nmin;
  473.  
  474.    /* Get the current time in minutes */
  475.    dostime (&cur_hour, &cur_minute, &junk, &junk);
  476.    our_time = cur_hour * 60 + cur_minute;
  477.  
  478.    /* Get the current day of the week */
  479.    dosdate (&cur_mon, &cur_mday, &cur_year, &cur_day);
  480.  
  481.    cur_day = 1 << cur_day;
  482.  
  483.    /* A ridiculous number */
  484.    time_to = 3000;
  485.  
  486.    /* Go through the events from top to bottom */
  487.    for (i = 0; i < num_events; i++)
  488.       {
  489.       /* If it is the current event, skip it */
  490.       if (cur_event == i)
  491.          continue;
  492.  
  493.       /* If it is a BBS event, skip it */
  494.       if (e_ptrs[i]->behavior & MAT_BBS)
  495.          continue;
  496.  
  497.       /* If it was already run today, skip it */
  498.       if (e_ptrs[i]->last_ran == cur_mday)
  499.          continue;
  500.  
  501.       /* If it doesn't happen today, skip it */
  502.       if (!(e_ptrs[i]->days & cur_day))
  503.          continue;
  504.  
  505.       /* If not this day of the month, skip it */
  506.       if ((e_ptrs[i]->day) && (e_ptrs[i]->day != (char)cur_mday))
  507.          continue;
  508.       
  509.       /* If not this month of the year, skip it */
  510.       if ((e_ptrs[i]->month) && (e_ptrs[i]->month != (char)cur_mon))
  511.          continue;
  512.  
  513.       /* If it is earlier than now, skip it unless it is forced */
  514.       if (e_ptrs[i]->minute < our_time)
  515.          {
  516.          if (!(e_ptrs[i]->behavior & MAT_FORCED))
  517.             {
  518.             continue;
  519.             }
  520.  
  521.          /* Hmm, found a forced event that has not executed yet */
  522.          /* Give the guy 2 minutes and call it quits */
  523.          guess = 2;
  524.          }
  525.       else
  526.          {
  527.          /* Calculate how far it is from now */
  528.          guess = e_ptrs[i]->minute - our_time;
  529.          }
  530.  
  531.       /* If less than closest so far, keep it */
  532.       if (time_to > guess)
  533.          time_to = guess;
  534.       }
  535.  
  536.    /* If we still have nothing, then do it again, starting at midnight */
  537.    if (time_to >= 1441)
  538.       {
  539.       /* Calculate here to midnight */
  540.       nmin = 1440 - our_time;
  541.  
  542.       /* Go to midnight */
  543.       our_time = 0;
  544.  
  545.       /* Go to the next possible day */
  546.       cur_day = cur_day << 1;
  547.       if (cur_day > DAY_SATURDAY)
  548.          cur_day = DAY_SUNDAY;
  549.  
  550.       /* Go through the events from top to bottom */
  551.       for (i = 0; i < num_events; i++)
  552.          {
  553.          /* If it is a BBS event, skip it */
  554.          if (e_ptrs[i]->behavior & MAT_BBS)
  555.             continue;
  556.  
  557.          /* If it doesn't happen today, skip it */
  558.          if (!(e_ptrs[i]->days & cur_day))
  559.             continue;
  560.  
  561.          /* If not this day of the month, skip it */
  562.          if ((e_ptrs[i]->day) && (e_ptrs[i]->day != (char)cur_mday))
  563.             continue;
  564.       
  565.          /* If not this month of the year, skip it */
  566.          if ((e_ptrs[i]->month) && (e_ptrs[i]->month != (char)cur_mon))
  567.             continue;
  568.  
  569.          /* Calculate how far it is from now */
  570.          guess = e_ptrs[i]->minute + nmin;
  571.  
  572.          /* If less than closest so far, keep it */
  573.          if (time_to > guess)
  574.             time_to = guess;
  575.          }
  576.       }
  577.  
  578.    if (time_to > 1440)
  579.       time_to = 1440;
  580.  
  581.    if (time_to < 1)
  582.       time_to = 1;
  583.  
  584.    return (time_to);
  585. }
  586.